import * as THREE from "three";
import Stats from "three/addons/libs/stats.module.js";
import { OrbitControls } from "three/addons/controls/OrbitControls.js";
import { FBXLoader } from "three/addons/loaders/FBXLoader.js";
// 创建场景对象
const scene = new THREE.Scene();
// 创建透视相机
const camera = new THREE.PerspectiveCamera(
  45,
  window.innerWidth / window.innerHeight,
  0.1,
  1000000
);
// 创建WebGL渲染器
const renderer = new THREE.WebGLRenderer({ antialias: true });
// 获取渲染帧
const clock = new THREE.Clock();
// 创建性能监控对象
const stats = new Stats();
// 创建轨道控制对象
const controls = new OrbitControls(camera, renderer.domElement);
// FBX文件加载器
const loader = new FBXLoader();
const meshName = "LiuQing";

const getAxesHelper = () => {
  // 创建辅助观察坐标系
  const axesHelper = new THREE.AxesHelper(200);
  scene.add(axesHelper);
};
const getMeshFun = () => {
  //   小圆柱几何体
  //   const geometrySphere = new THREE.CylinderGeometry(0.5, 0.5, 0.5);
  // 创建立方体几何对象
  // 创建材质对象
  // 创建多个使用不同材质的网格模型，并沿x、y、z轴分布
  // 创建立方体几何对象
  const geometry = new THREE.BoxGeometry(1, 1, 1);

  function getRandomRGBColor() {
    // 生成随机的红、绿、蓝值
    const r = Math.floor(Math.random() * 256);
    const g = Math.floor(Math.random() * 256);
    const b = Math.floor(Math.random() * 256);
    return `rgb(${r}, ${g}, ${b})`;
  }

  // 示例
  // 函数用于创建并设置网格模型
  function createMesh(material, position, name) {
    const mesh = new THREE.Mesh(geometry, material);
    mesh.name = name;
    mesh.position.set(...position);
    scene.add(mesh);
  }

  // 创建多个使用不同材质的网格模型，并沿x、y、z轴分布
  for (let i = 0; i < 10; i++) {
    const MaterialProObj = {
      color: getRandomRGBColor(),
      side: THREE.DoubleSide,
    };
    // x上的网格模型
    //   创建材质对象
    createMesh(
      new THREE.MeshBasicMaterial(MaterialProObj),
      [5 + i * 3, 0.1, 0],
      meshName
    );
    // y上的网格模型
    createMesh(
      new THREE.MeshBasicMaterial(MaterialProObj),
      [0, i * 3, 0],
      meshName
    );
    // z上的网格模型
    createMesh(
      new THREE.MeshBasicMaterial(MaterialProObj),
      [0, 0, i * 3],
      meshName
    );
  }
};

camera.position.set(50, 20, 50);
// camera.up.x = 0;
// camera.up.y = 0;
// camera.up.z = 1;
camera.lookAt(new THREE.Vector3(5, 0, 5));
document.body.appendChild(stats.domElement);
renderer.setSize(window.innerWidth, window.innerHeight);
document.body.appendChild(renderer.domElement);

const getSceneFun = () => {
  // 场景背景色
  scene.background = new THREE.Color(0xa0a0a0);
  // 创建网格
  const grid = new THREE.GridHelper(200, 100, 0x000000, 0x000000);
  grid.material.opacity = 0.2;
  grid.material.transparent = true;
  scene.add(grid);
  // 创建平面底色
  const mesh = new THREE.Mesh(
    new THREE.PlaneGeometry(200, 200),
    new THREE.MeshPhongMaterial({ color: 0x999999, depthWrite: false })
  );
  mesh.rotation.x = -Math.PI / 2;
  mesh.receiveShadow = true;
  scene.add(mesh);

  // 自然环境光
  const hemiLight = new THREE.HemisphereLight(0xffffff, 0x444444, 4);
  hemiLight.position.set(0, 200, 0);
  scene.add(hemiLight);
  // 增加平行光
  // 创建一个方向光（DirectionalLight）
  const dirLight = new THREE.DirectionalLight(0xffffff, 4); // 颜色为白色（0xffffff），强度为 4
  dirLight.position.set(0, 200, 100); // 设置光源的位置，坐标为 (0, 200, 100)
  dirLight.castShadow = true; // 启用阴影投射

  // // 配置光源的阴影相机参数
  // dirLight.shadow.camera.top = 180; // 设置阴影相机的顶部边界
  // dirLight.shadow.camera.bottom = -100; // 设置阴影相机的底部边界
  // dirLight.shadow.camera.left = -120; // 设置阴影相机的左侧边界
  // dirLight.shadow.camera.right = 120; // 设置阴影相机的右侧边界

  // 将方向光添加到场景中
  scene.add(dirLight);
};

// 管理对象的动画
let mixer = null;
// 存储动画对象
let object = null;
// 当前动画
let action = null
// 当前播放的哪个动画
let actionFlag = 0
function loadAsset(asset) {
  loader.load("./test/FBX/Samba Dancing.fbx", function (group) {
    // name属性
    group.name = "LiuQing_Name";
    object = group;
    // 设置小人位置
    object.position.set(5, 0, 5);
    // 缩小比例展示
    object.scale.setScalar(0.05);
   
    if (object.animations && object.animations.length) {
      // 创建一个 AnimationMixer 实例，用于管理对象的动画
      mixer = new THREE.AnimationMixer(object);
      // 选择要播放的动画剪辑
      // object.animations[0] 是跳舞的动画，object.animations[1] 是站立的动画
       action = mixer.clipAction(object.animations[0]);

      // 播放选定的动画
      action.play();
    } else {
      mixer = null;
    }
    scene.add(object);
  });
}
// 动画函数，用于不断更新场景和渲染
const animate = () => {
  stats.update();
  //   只有mesh名字name为LiuQing的旋转
  scene.children.forEach((i) => {
    if (i.type === "Mesh" && i.isMesh && i.name === meshName) {
      i.rotateY(0.01);
    }
  });
  //   getDelta 方法用于获取自上次调用 getDelta 以来经过的时间
  const delta = clock.getDelta();
  if (mixer) mixer.update(delta);
  controls.update();
  renderer.render(scene, camera);
  requestAnimationFrame(animate);
};

// 增加点击事件

// 创建 Raycaster 对象
const raycaster = new THREE.Raycaster();
const mouse = new THREE.Vector2();

// 处理鼠标点击事件
function onMouseClick(event) {
  // 计算鼠标在屏幕上的位置
  mouse.x = (event.clientX / window.innerWidth) * 2 - 1;
  mouse.y = -(event.clientY / window.innerHeight) * 2 + 1;

  // 更新 Raycaster 的射线
  raycaster.setFromCamera(mouse, camera);

  // 检测射线与场景中的对象是否相交
  const intersects = raycaster.intersectObjects(scene.children);
  // console.log(intersects);
  if (intersects.length > 0) {
    // 如果有相交的对象，改变其颜色
    // intersects[0].object.material.color.set(0xff0000); // 改变颜色为红色
    const thisObject = intersects[0].object;
    if (
      thisObject.isMesh &&
      thisObject?.parent?.name === 'LiuQing_Name'
    ) {
      // 先停止之前的动画播放
       action.stop();
       console.log('当前小机器人对象：',object)
       action = mixer && mixer.clipAction(object.animations[actionFlag === 0 ? 1 : 0]);
       actionFlag = actionFlag === 0 ? 1 : 0
      // 播放选定的动画
      action && action.play();
    }
  }
}

// 添加鼠标点击事件监听器
document.addEventListener("click", onMouseClick, false);
const iniFun = () => {
  loadAsset();
  getSceneFun();
  getAxesHelper();
  getMeshFun();
};
iniFun();
animate();
